package vn.edu.saigontech.ncms.web.offering.report;

import java.util.ArrayList;
import java.util.Collection;
import java.util.Date;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;

import vn.edu.saigontech.ncms.model.info.Offering;
import vn.edu.saigontech.ncms.model.system.Room;
import vn.edu.saigontech.ncms.model.system.Shift;
import vn.edu.saigontech.ncms.service.OfferingService;
import vn.edu.saigontech.ncms.service.RoomService;
import vn.edu.saigontech.ncms.service.ShiftService;
import vn.edu.saigontech.ncms.util.CollectionUtil;
import vn.edu.saigontech.ncms.util.DateUtil;

public class ClassroomScheduleReport {
	private LinkedList<Date> range = new LinkedList<Date>();
	private List<RoomScheduleDetail> roomSchedules = new ArrayList<RoomScheduleDetail>();
	private Map<Date, ShiftMap> scheduleMap = new HashMap<Date, ShiftMap>();
	
	public ClassroomScheduleReport(Date fromDate, Date toDate) {
		this.range = new LinkedList<Date>(DateUtil.sequenceAsList(fromDate, toDate));
		this.init();
	}

	private void init() {
		List<Room> rooms = new ArrayList<Room>(RoomService.INSTANCE.findAllAreActive());
		Collection<Offering> offerings = OfferingService.INSTANCE.findByDate(range.getFirst(), range.getLast());
		this.scheduleMap = CollectionUtil.createScheduleMap(range);
		for(Room room : rooms) {
			RoomScheduleDetail roomSchedule = new RoomScheduleDetail(room);
			List<Shift> shifts = this.createShifts();
			for(Shift shift : shifts) {
				ShiftScheduleDetail shiftSchedule = new ShiftScheduleDetail(shift);
				for(Date date : range) {
					boolean exist = this.checkExistStudyAtShift(shiftSchedule, offerings, date, shift, room);
					shiftSchedule.put(date, exist);
					if(exist) {
						int count = scheduleMap.get(date).get(shift.getName()) + 1;
						scheduleMap.get(date).put(shift.getName(), count);
					}
				}
				roomSchedule.addShiftScheduleDetail(shiftSchedule);
			}
			this.addRoomScheduleDetail(roomSchedule);
		}
	}
	
	private boolean checkExistStudyAtShift(ShiftScheduleDetail shiftSchedule, Collection<Offering> offerings, Date date, Shift shift, Room room) {
		for(Offering offering : offerings) {
			if(offering.checkExistStudyShift(date, shift, room)) {
				shiftSchedule.putTmp(date, offering.getName());
				return true;
			}
		}
		return false;
	}
	
	private List<Shift> createShifts() {
		List<Shift> ret = new ArrayList<Shift>();
		ret.add(ShiftService.INSTANCE.findById(1l));
		ret.add(ShiftService.INSTANCE.findById(2l));
		return ret;
	}
	
	private void addRoomScheduleDetail(RoomScheduleDetail detail) {
		this.roomSchedules.add(detail);
	}
	
	public String getDate() {
		String pattern = "dd/MM/yyyy";
		String startDate = DateUtil.toString(range.getFirst(), pattern);
		String endDate = DateUtil.toString(range.getLast(), pattern);
		return startDate + " - " + endDate;
	}

	public LinkedList<Date> getRange() {
		return range;
	}

	public void setRange(LinkedList<Date> range) {
		this.range = range;
	}

	public List<RoomScheduleDetail> getRoomSchedules() {
		return roomSchedules;
	}

	public void setRoomSchedules(List<RoomScheduleDetail> roomSchedules) {
		this.roomSchedules = roomSchedules;
	}

	public Map<Date, ShiftMap> getScheduleMap() {
		return scheduleMap;
	}

	public void setScheduleMap(Map<Date, ShiftMap> scheduleMap) {
		this.scheduleMap = scheduleMap;
	}
}
